package com.gxks.lhs.controller.user;

import com.gxks.lhs.DTO.LoginDTO;
import com.gxks.lhs.DTO.updatePasswordDTO;
import com.gxks.lhs.constants.R;
import com.gxks.lhs.entity.User;
import com.gxks.lhs.security.SecurityConfig;
import com.gxks.lhs.security.SecurityUtils;
import com.gxks.lhs.service.IGoodsService;
import com.gxks.lhs.service.IUserService;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.util.StringUtils;
import org.springframework.web.bind.annotation.*;

import java.math.BigDecimal;
import java.util.Objects;
import java.util.concurrent.TimeUnit;
import java.util.regex.Pattern;

@Api(tags = "用户管理模块")
@Slf4j
@RestController
@RequestMapping("/restful-api/user")
public class UserInfoContrller {
    @Autowired
    private IUserService userService;
    @Autowired
    private IGoodsService goodsService;
    @Autowired
    private SecurityConfig securityConfig;
    @Autowired
    private StringRedisTemplate stringRedisTemplate;

    Pattern pattern = Pattern.compile("0?(13|14|15|17|18|19)[0-9]{9}");


    @ApiOperation("生成注册短信验证码")
    @GetMapping("/getRegCode")
    public R getCode(@RequestParam String phone) {
        if (!pattern.matcher(phone).matches()) {
            return R.error("手机号格式错误");
        }
        if (userService.isExist(phone)) {
            return R.error("该手机号已被注册");
        } else {
            String code = (Math.random() + "").substring(3, 9);
            stringRedisTemplate.opsForValue().set("register:" + phone, code, 15, TimeUnit.MINUTES);
            log.info(phone + "的短信验证码：" + code);
            return R.success(code);
        }
    }

    /**
     * 用户注册接口
     *
     * @param loginDTO 包含用户注册所需信息的数据传输对象，包括手机号、密码、验证码等。
     * @return R 返回一个结果对象，可能包含注册成功或失败的信息。
     */
    @ApiOperation("用户注册")
    @PostMapping("/register")
    public R register(@RequestBody LoginDTO loginDTO) {
        if (loginDTO.getPhone() == null || loginDTO.getPassword() == null) {
            return R.error("手机号或密码不能为空");
        }
        if (loginDTO.getCode() == null) {
            return R.error("验证码不能为空");
        }
        // 验证手机号格式是否正确
        if (!pattern.matcher(loginDTO.getPhone()).matches()) {
            return R.error("手机号格式错误");
        }
        // 检查手机号是否已被注册
        if (userService.isExist(loginDTO.getPhone())) {
            return R.error("该手机号已被注册");
        }
        // 验证验证码是否正确及有效
        if (Objects.equals(loginDTO.getCode(), "888888")) {
            // 测试使用的固定验证码
        } else if (stringRedisTemplate.opsForValue().get("register:" + loginDTO.getPhone()) == null) {
            return R.error("验证码已过期");
        } else if (!stringRedisTemplate.opsForValue().get("register:" + loginDTO.getPhone()).equals(loginDTO.getCode())) {
            return R.error("验证码错误");
        }
        // 创建用户对象并设置基本信息
        User user = new User();
        user.setUsername("用户" + loginDTO.getPhone().substring(7));
        user.setNickname("用户" + loginDTO.getPhone().substring(7));
        user.setPhone(loginDTO.getPhone());
        // 使用密码加密器对密码进行加密
        user.setPassword(securityConfig.passwordEncoder().encode(loginDTO.getPassword()));
        // 添加用户到数据库
        return userService.addUser(user) ? R.success() : R.error("注册失败");
    }


    /**
     * 根据id获取用户信息
     */
    @ApiOperation(value = "根据id获取用户信息")
    @GetMapping("/getUserInfo")
    public R getUserById() {
        String id = SecurityUtils.getCurrentUserId();
        User user = userService.getUserById(id);
        if (user != null) {
            user.setPassword(null);
            return R.success(user, "查询成功");
        }
        return R.error("查询失败，返回null");
    }

    /**
     * 根据id修改用户的信息
     */
    @ApiOperation(value = "修改用户信息")
    @PutMapping("/updateUser")
    public R updateUserById(@RequestBody User user) {
        String id = SecurityUtils.getCurrentUserId();
        user.setId(id);
        if (userService.updateUser(user)) {
            return R.success().setMsg("修政成功");
        }
        return R.error("修政失败");
    }

    @ApiOperation("注销账户")
    @DeleteMapping("/delete")
    public R deleteUserById() {
        String id = SecurityUtils.getCurrentUserId();
        if (userService.deleteUser(id)) {
            return R.success().setMsg("删除成功");
        }
        return R.error("删除失败");
    }

    @ApiOperation("根据二手手机id获取卖家手机")
    @GetMapping("/getPhone")
    public R getSellerPhone(String goodsId) {
        String sellerId = goodsService.findUserIdByGoodsId(goodsId);
        String phone = userService.getPhoneByUserId(sellerId);
        if (phone != null) {
            return R.success(phone, "查询成功");
        }
        return R.error("查询失败，返回null");
    }

    /**
     * 修改密码
     *
     * @param updatePassword 包含旧密码、新密码和确认新密码的信息对象
     * @return 返回操作结果，成功则包含成功信息，失败则包含失败原因
     */
    @ApiOperation("修改密码")
    @PutMapping("/updatePassword")
    public R updatePassword(@RequestBody updatePasswordDTO updatePassword) {
        // 获取当前登录用户的ID
        String id = SecurityUtils.getCurrentUserId();
        // 根据ID获取用户对象
        User user = userService.getUserById(id);
        // 用户不存在时返回错误信息
        if (user == null) {
            return R.error("用户不存在");
        }
        // 新旧密码为空时返回错误信息
        if (updatePassword.getNewPassword() == null || updatePassword.getOldPassword() == null) {
            return R.error("密码不能为空");
        }
        // 新密码和确认密码不一致时返回错误信息
        if (!updatePassword.getNewPassword().equals(updatePassword.getConfirmPassword())) {
            return R.error("两次密码不一致");
        }
        // 验证旧密码是否正确
        if (securityConfig.passwordEncoder().matches(updatePassword.getOldPassword(), user.getPassword())) {
            // 更新用户密码
            user.setPassword(securityConfig.passwordEncoder().encode(updatePassword.getNewPassword()));
            // 保存更新后的用户信息
            if (userService.updateUserPassword(user)) {
                return R.success().setMsg("修改成功");
            } else {
                return R.error("修改失败");
            }
        } else {
            return R.error("旧密码错误");
        }

    }

    @ApiOperation("获取用户的余额")
    @GetMapping("/getBalance")
    public R getBalance() {
        String userId = SecurityUtils.getCurrentUserId();
        BigDecimal balance = userService.getBalanceByUserId(userId);
        if (balance != null)
            return R.success(balance, "获取成功");
        return R.error("获取失败");
    }

    @ApiOperation("提现")
    @PostMapping("/withdraw")
    public R withdraw(@RequestParam BigDecimal amount) {
        String userId = SecurityUtils.getCurrentUserId();
        // 非空校验
        if (StringUtils.isEmpty(amount)) {
            return R.error("请输入提现金额");
        }

        // 正数校验
        if (amount.signum() < 1) { // signum() 返回值：1（正数）、-1（负数）、0（零）
            return R.error("提现金额必须为正数");
        }

//        校验只能两位小数
        if (amount.scale() > 2) {
            return R.error("提现金额最多只能保留两位小数");
        }

        if (userService.withdraw(userId, amount))
            return R.success().setMsg("提现成功");
        return R.error("提现失败");
    }

    @ApiOperation("充值")
    @PostMapping("/recharge")
    public R recharge(@RequestParam BigDecimal amount) {
        String userId = SecurityUtils.getCurrentUserId();
        // 非空校验
        if (StringUtils.isEmpty(amount)) {
            return R.error("请输入提现金额");
        }

        // 正数校验
        if (amount.signum() < 1) { // signum() 返回值：1（正数）、-1（负数）、0（零）
            return R.error("提现金额必须为正数");
        }

//        校验只能两位小数
        if (amount.scale() > 2) {
            return R.error("提现金额最多只能保留两位小数");
        }

        if (userService.recharge(userId, amount))
            return R.success().setMsg("提现成功");
        return R.error("提现失败");
    }
}
